#include "server.hpp"

Server::Server()
{
    privateKey =  "../server/server-key.pem";
    localCertificate = "../server/server-crt.pem";

    // Initializes the server with default settings
    start(QHostAddress::Any, 45434);
    
    connectedClients = new QMap<QSslSocket*,int>;
}


Server::Server(quint16 port)
{
    start(QHostAddress::Any, port);
}

Server::~Server()
{}


void Server::start(QHostAddress host, quint16 port)
{
    // Listen for connexion
    listen(host, port);
}

void Server::incomingConnection(int socketDescriptor)
 {
     serverSocket = new QSslSocket;

     if(serverSocket->setSocketDescriptor(socketDescriptor))
     {
         // Load private key
         QFile file(privateKey);
         if( !file.open(QIODevice::ReadOnly))
         {
             // Debug
             display("Unable to open : " + privateKey);
             exit(0);
         }

         // passphrase : DefiQt
         QSslKey key(&file, QSsl::Rsa, QSsl::Pem, QSsl::PrivateKey, "defiQt" );
         file.close();

         serverSocket->setPrivateKey(key);

         // Load certificate
         if( !serverSocket->addCaCertificates("../ca/ca.pem"))
         {
             // Debug
             display("Unable to open CA certificate : ../ca/ca.pem");
             exit(0);
         }

         // Load server's certificate
         serverSocket->setLocalCertificate(localCertificate);

         // Don't verify client's identity
         serverSocket->setPeerVerifyMode(QSslSocket::VerifyNone);

         // Connections and disconnections signals
         connect(serverSocket, SIGNAL(readyRead()), this, SLOT(read()));
         connect(serverSocket, SIGNAL(disconnected()), this, SLOT(disconnected()));

         serverSocket->ignoreSslErrors();
         serverSocket->startServerEncryption();
         
         display("New client connected.");
     }
     else
     {
         delete serverSocket;
     }
 }


void Server::read()
{
	// Find who is sending
	QSslSocket *client = qobject_cast<QSslSocket*>(sender());

	// Print the sender
	display("A client is writing on the socket.");

	// If whe can't know who has sending data -> break
	if(client == 0)
		return;

	// Login process
	QStringList package;

	QString data = serverSocket->readAll();
	package = data.split(":");
        qDebug() << package;
	QString command = package[0];
	package.removeFirst();

        // Read the command in package[0]

        if(command == "login")
        {
                display("Login request.");
                PackageManager::login(package,client,connectedClients);
        }

	if(command == "ecg")
	{
	    display("Ecg request with file :"+package[0]);
	    PackageManager::ecg(package, client);
	}

}

void Server::disconnected()
{
    // Find who is disconnecting
    QSslSocket *client = qobject_cast<QSslSocket*>(sender());

    if(client == 0)
            return;

    // Print the sender
    display("Client disconnected.");
    connectedClients->remove(client);

    // Deletes the socket
    client->deleteLater();
}

void Server::display(QString s)
{
	qDebug() << s;
}
